
package common;

import common.packet.ClientInfo;
import common.packet.Packet;
import common.packet.PacketFactory;
import java.io.DataInputStream;
import java.io.DataOutputStream;
import java.io.IOException;
import java.net.Socket;
import java.net.SocketException;

/**
 * Stores information about a client and has thread safe methods to read/write
 * packets from/to its socket.
 * 
 * @author xissburg
 */
public class Client
{
    private final Socket socket;
    private final DataInputStream in;
    private final DataOutputStream out;
    private final ClientInfo clientInfo;
    private final PacketFactory packetFactory;

    public Client(Socket socket) throws IOException
    {
        this.socket = socket;
        out = new DataOutputStream(socket.getOutputStream());
        in = new DataInputStream(socket.getInputStream());
        clientInfo = new ClientInfo();
        packetFactory = new PacketFactory();
    }

    public Packet read() throws IOException, IllegalArgumentException
    {
        synchronized(in)
        {
            return packetFactory.readPacket(in);
        }
    }

    public void write(Packet packet) throws IOException
    {
        synchronized(out)
        {
            packet.write(out);
        }
    }

    public void setSocketTimeout(int timeout) throws SocketException
    {
        synchronized(socket)
        {
            socket.setSoTimeout(timeout);
        }
    }

    public int getSocketTimeout() throws SocketException
    {
        int timeout = 0;

        synchronized(socket)
        {
            timeout = socket.getSoTimeout();
        }

        return timeout;
    }
    
    public void closeSocket() throws IOException
    {
        socket.close();
    }

    public ClientInfo getClientInfo() {
        return clientInfo;
    }
}
